package com.jinzhi.jzweb.strategy.impl;

import com.baomidou.mybatisplus.mapper.EntityWrapper;
import com.baomidou.mybatisplus.mapper.Wrapper;
import com.baomidou.mybatisplus.plugins.Page;
import com.jinzhi.common.base.BaseController;
import com.jinzhi.common.utils.Result;
import com.jinzhi.jzweb.domain.ExaminationResultsComDO;
import com.jinzhi.jzweb.domain.StuSignUpComDO;
import com.jinzhi.jzweb.domain.moduleConfig.CareStuSignUpComRealityDO;
import com.jinzhi.jzweb.pojo.moduleConfig.RecordPointsDO;
import com.jinzhi.jzweb.pojo.moduleConfig.SourVo;
import com.jinzhi.jzweb.pojo.moduleConfig.SourVoA;
import com.jinzhi.jzweb.pojo.statistics.StuResultsAVo;
import com.jinzhi.jzweb.pojo.statistics.StuResultsHeaderVo;
import com.jinzhi.jzweb.pojo.statistics.StuResultsTeamAVo;
import com.jinzhi.jzweb.service.ExaminationResultsComService;
import com.jinzhi.jzweb.service.StuSignUpComService;
import com.jinzhi.jzweb.service.moduleConfig.CareStuSignUpComRealityService;
import com.jinzhi.jzweb.service.moduleConfig.DecryptService;
import com.jinzhi.jzweb.strategy.BaseStrategy;
import com.jinzhi.jzweb.utils.EasyPoiUtil;
import org.apache.commons.lang.StringUtils;
import org.apache.poi.ss.formula.functions.T;
import org.springframework.stereotype.Component;
import org.springframework.transaction.annotation.Transactional;

import javax.servlet.http.HttpServletResponse;
import java.math.BigDecimal;
import java.math.RoundingMode;
import java.text.DecimalFormat;
import java.util.*;
import java.util.stream.Collectors;

/*
 *  @author : JingChangTian
 *  @date   : 2023/8/11 20:20
 *  @description :  A赛场
 *
 */
@Component(value = "A")
public class ExaminationASour extends BaseController implements BaseStrategy  {


    private final ExaminationResultsComService examinationResultsComService;

    private final DecryptService decryptService;

    private final StuSignUpComService stuSignUpComService;

    private final CareStuSignUpComRealityService careStuSignUpComRealityService;


    public ExaminationASour(ExaminationResultsComService examinationResultsComService,
                            DecryptService decryptService, StuSignUpComService stuSignUpComService, CareStuSignUpComRealityService careStuSignUpComRealityService) {
        this.examinationResultsComService = examinationResultsComService;
        this.decryptService = decryptService;
        this.stuSignUpComService = stuSignUpComService;
        this.careStuSignUpComRealityService = careStuSignUpComRealityService;
    }


    @Override
    public void downloadImportTemplate(HttpServletResponse response,String field) {
        List<SourVo> asourVos = new ArrayList<>();
        //根据赛场查询成绩信息
        List<ExaminationResultsComDO> examinationResultsComDOS = examinationResultsComService.selectList(new EntityWrapper<ExaminationResultsComDO>()
                .eq("field",field).ne("score1",-1));
        if(examinationResultsComDOS.isEmpty()){
            return;
        }
        examinationResultsComDOS.forEach(a ->{
            SourVo sourVo = new SourVo();
            sourVo.setScore1((new DecimalFormat("0.00").format(a.getScore1())));
            sourVo.setScore2((new DecimalFormat("0.00").format(a.getScore2())));
            sourVo.setScore3((new DecimalFormat("0.00").format(a.getScore3())));
            sourVo.setScore4(a.getScore4()==-1?"-": (new DecimalFormat("0.00").format(a.getScore4())));
            sourVo.setScore5(a.getScore5()==-1?"-": (new DecimalFormat("0.00").format(a.getScore5())));
            sourVo.setRemarkA(a.getRemarkA());
            sourVo.setNum2(a.getNum2());
            asourVos.add(sourVo);
        });
        //导出操作
        EasyPoiUtil.exportExcel(asourVos, "婴幼儿早期教育发展分析选择二次加密与分数信息", "婴幼儿早期教育发展分析选择二次加密与分数信息", SourVo.class, "婴幼儿早期教育发展分析选择二次加密与分数信息", response);
    }

    @Override
    public void downloadImportBased(HttpServletResponse response, String field) {
        List<SourVoA> asourVos = new ArrayList<>();
        //根据赛场查询成绩信息
        List<ExaminationResultsComDO> examinationResultsComDOS = examinationResultsComService.selectList(new EntityWrapper<ExaminationResultsComDO>()
                .eq("field",field));
        if(examinationResultsComDOS.isEmpty()){
            return;
        }
        examinationResultsComDOS.forEach(a ->{
            SourVoA sourVo = new SourVoA();
            sourVo.setTotalScore((new DecimalFormat("0.00").format(a.getTotalScore())));
            sourVo.setNum2(a.getNum2());
            asourVos.add(sourVo);
        });
        //导出操作
        EasyPoiUtil.exportExcel(asourVos, "婴幼儿照护知识素养测评二次加密与分数信息", "婴幼儿照护知识素养测评二次加密与分数信息", SourVoA.class, "婴幼儿照护知识素养测评二次加密与分数信息", response);
    }

    @Transactional
    @Override
    public Result recordPoints(RecordPointsDO resultsComDO) {
        //根据赛场+二次加密验证是否有成绩信息
        List<ExaminationResultsComDO> examinationResultsComDOS = examinationResultsComService.selectList(new EntityWrapper<ExaminationResultsComDO>()
                .eq(StringUtils.isNotBlank(resultsComDO.getNum2()),"num2",resultsComDO.getNum2())
                .eq("field",resultsComDO.getField()));
        ExaminationResultsComDO resultsComDO1 = new ExaminationResultsComDO();
        //赋予分数
        resultsComDO1.setNum2(resultsComDO.getNum2());
        resultsComDO1.setField(resultsComDO.getField());
        resultsComDO1.setScore1(resultsComDO.getModuleOneMarkOne());
        resultsComDO1.setScore2(resultsComDO.getModuleOneMarkTwo());
        resultsComDO1.setScore3(resultsComDO.getModuleOneMarkThree());
        resultsComDO1.setScore4(null==resultsComDO.getModuleOneMarkFour()?-1:resultsComDO.getModuleOneMarkFour());
        resultsComDO1.setScore5(null==resultsComDO.getModuleOneMarkFive()?-1:resultsComDO.getModuleOneMarkFive());
        resultsComDO1.setRemarkA(resultsComDO.getRemark());
        //修改一二次加密状态为已录分
//        DecryptDO decryptDO = new DecryptDO();
//        decryptDO.setNum2s(resultsComDO.getNum2());
//        decryptDO.setField(resultsComDO.getField());
//        decryptDO  = decryptService.selectOne(decryptDO);
//        decryptDO.setStatus(2);
//        decryptService.updateById(decryptDO);

        StuSignUpComDO stuSignUpComDO = new StuSignUpComDO();
        stuSignUpComDO.setNum2(resultsComDO.getNum2());
        stuSignUpComDO.setCompetitionType(2);
        StuSignUpComDO stuSignUpComDO1 = stuSignUpComService.selectOne(stuSignUpComDO);
        stuSignUpComDO1.setStatus(2);
        stuSignUpComService.updateById(stuSignUpComDO1);

        if(examinationResultsComDOS.isEmpty()){
            //新增
            return Result.ok(examinationResultsComService.insert(resultsComDO1));
        }
        //修改
        return Result.ok(examinationResultsComService.update(resultsComDO1,new EntityWrapper<ExaminationResultsComDO>().eq("num2",resultsComDO.getNum2())
                .eq("field",resultsComDO.getField())));
    }

    @Override
    public Result getScoreInfoPage(String field, Integer current, Integer size,Integer status) {

        Page<ExaminationResultsComDO> page = new Page<ExaminationResultsComDO>(current,size);
        Wrapper werr = new EntityWrapper<ExaminationResultsComDO>();
        if(status == 1){
            werr.ne("score1",-1);
        }
        //查询已经匹配的解密列表
        Page<ExaminationResultsComDO> resultsComDOPage =
                examinationResultsComService.selectPage(page,werr.eq("field",field));
        List<ExaminationResultsComDO> records = resultsComDOPage.getRecords();
        if(records!=null && !records.isEmpty()){
            for (ExaminationResultsComDO record : records) {
                if(record.getScore4()<0){
                    record.setScore4(null);
                }
                if(record.getScore5()<0){
                    record.setScore5(null);
                }
            }
        }
        return Result.ok(resultsComDOPage);
    }

    @Override
    public Page getStatisticsByfield(String field, Integer current, Integer size,Integer decryptAll) {
        //分页查询已经解密的团队信息
        Page<StuResultsTeamAVo> teamPage = careStuSignUpComRealityService.getTeam(current, size,null,1);
        if(teamPage.getRecords().isEmpty()){
            return teamPage;
        }
        //获取团队名称集合
        List<String> nameTeams = teamPage.getRecords().stream().map(StuResultsTeamAVo::getUnitName).collect(Collectors.toList());
        //根据团队、赛场查询选手成绩信息
        List<StuResultsAVo>  stuResultsAVos = examinationResultsComService.getStatisticsByfieldStuIds(field,nameTeams);
        //拼接团队选手信息
        teamPage.getRecords().forEach(a->{
            a.setStuResultsAVos(stuResultsAVos.stream().filter(b-> b.getUnitName().equals(a.getUnitName())).collect(Collectors.toList()));
        });
        //计算团队得分
        for (int i = 0; i < teamPage.getRecords().size(); i++) {
            Double teamsCore = 0.00;
            for (int j = 0; j < teamPage.getRecords().get(i).getStuResultsAVos().size(); j++) {
                teamsCore = teamsCore +
                        Optional.of(Double.parseDouble(teamPage.getRecords().get(i).getStuResultsAVos().get(j).getTotalScore())).orElse(0.00) +
                        Optional.of(Double.parseDouble(teamPage.getRecords().get(i).getStuResultsAVos().get(j).getStudy())).orElse(0.00);
            }
            if(teamsCore!=0.0){
                teamPage.getRecords().get(i).setTeamsCore(new BigDecimal(teamsCore).divide(BigDecimal.valueOf(teamPage.getRecords().get(i).getStuResultsAVos().size()),
                        2, RoundingMode.HALF_UP).toString());
            }else{
                teamPage.getRecords().get(i).setTeamsCore(new DecimalFormat("0.00").format(teamsCore));
            }

        }
        return teamPage;
    }

    @Override
    public void getStatisticsDownload(HttpServletResponse response,String field) {
        Page<StuResultsTeamAVo> list = getStatisticsByfield(field,1,1000,1);
        EasyPoiUtil.exportExcel(list.getRecords(), "婴幼儿照护综合知识测评成绩导出", "婴幼儿照护综合知识测评成绩导出", StuResultsTeamAVo.class, "婴幼儿照护综合知识测评成绩导出", response);
    }

    @Override
    public Result<StuResultsHeaderVo> getStuResulteHeader(String field) {
        //获取理论团队得分信息
        Page<StuResultsTeamAVo> list = getStatisticsByfield(field,1,1000,null);
        if(list.getRecords().isEmpty()){
            return Result.ok(new StuResultsHeaderVo());
        }
        //竞赛人数QW
        Integer numberPepole = Math.toIntExact(list.getRecords().stream().count());
        //最高分
        Double highestScore = list.getRecords().stream().mapToDouble(value -> Double.parseDouble(value.getTeamsCore())).max().orElse(0);
        //最低分
        Double lowestScore = list.getRecords().stream().mapToDouble(value -> Double.parseDouble(value.getTeamsCore())).min().orElse(0);
        return Result.ok(new StuResultsHeaderVo(numberPepole,highestScore,lowestScore));
    }


}
